﻿using MaterialDesignExtensions.Controls;
using MaterialDesignThemes.Wpf;
using Newtonsoft.Json.Serialization;
using Newtonsoft.Json;
using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading.Tasks;
using AJWPFAdmin.Core.Validation;
using System.Reflection;
using System.IO;
using System.Windows.Media.Imaging;
using ICSharpCode.SharpZipLib.Zip;
using Microsoft.AspNetCore.Hosting.Server;
using AJWPFAdmin.Core.Logger;
using System.Net;
using System.Collections.ObjectModel;
using AngleSharp.Text;
using AJWPFAdmin.Core.ExtensionMethods;
using System.Diagnostics;
using System.Windows.Controls;
using System.Windows.Media;
using System.Windows;
using System.Net.Http;
using AJWPFAdmin.Core.Components.Views;
using Microsoft.Xaml.Behaviors.Media;
using Microsoft.AspNetCore.Mvc;
using Masuit.Tools.Security;
using System.Management;
using System.Drawing.Imaging;
using System.Drawing;
using DocumentFormat.OpenXml.Drawing.Charts;
using Microsoft.Win32;
using System.Net.NetworkInformation;

namespace AJWPFAdmin.Core.Utils
{
    public static class CommonUtil
    {
        public static AJLog4NetLogger Logger;

        public static readonly JsonSerializerSettings CAMELCASEJSONSERIALIZERSETTINGS = new()
        {
            DateFormatString = "yyyy-MM-dd HH:mm:ss",
            ReferenceLoopHandling = ReferenceLoopHandling.Ignore,
            ContractResolver = new CamelCasePropertyNamesContractResolver(),//new DefaultContractResolver()
            NullValueHandling = NullValueHandling.Include,
            //Converters = new List<JsonConverter> { new Int64ToStringConverter() },
        };

        public static readonly JsonSerializerSettings DEFAULTJSONSERIALIZERSETTINGS = new()
        {
            DateFormatString = "yyyy-MM-dd HH:mm:ss",
            ReferenceLoopHandling = ReferenceLoopHandling.Ignore,
            ContractResolver = new CamelCasePropertyNamesContractResolver(),//new DefaultContractResolver()
            NullValueHandling = NullValueHandling.Include,
            //Converters = new List<JsonConverter> { new Int64ToStringConverter() },
        };

        public static readonly ObservableCollection<string> CARNOPREFIX = new ObservableCollection<string>(new string[]
        {
            "京",
            "津",
            "沪",
            "渝",
            "冀",
            "豫",
            "云",
            "辽",
            "黑",
            "湘",
            "皖",
            "鲁",
            "新",
            "苏",
            "浙",
            "赣",
            "鄂",
            "桂",
            "甘",
            "晋",
            "蒙",
            "陕",
            "吉",
            "闽",
            "贵",
            "粤",
            "青",
            "藏",
            "川",
            "宁",
            "琼",
            "使",
            "领",
            "无"
        });

        public static HttpClient CreateCommonHttpClient(double secondsOfTimeout = 30)
        {
            return new HttpClient(new HttpClientHandler { UseProxy = false }, true)
            {
                Timeout = TimeSpan.FromSeconds(secondsOfTimeout)
            };
        }

        /// <summary>
        /// 无损压缩图片,返回压缩后的图片流
        /// </summary>
        /// <param name="stream">图片流</param>
        /// <param name="flag">压缩质量（数字越小压缩率越高）1-100</param>
        /// <param name="size">压缩后图片的最大大小, kb</param>
        /// <param name="firstCall">是否是第一次调用</param>
        /// <returns></returns>
        public static Stream CompressImage(Stream stream, int flag = 90, int size = 200, bool firstCall = true)
        {
            if (stream == null)
            {
                return null;
            }
            if (firstCall == true && stream.Length < size * 1024)
            {
                return stream;
            }
            System.Drawing.Image iSource = null;
            Bitmap ob = null;
            Stream result = null;
            try
            {
                iSource = System.Drawing.Image.FromStream(stream);
                ImageFormat tFormat = iSource.RawFormat;
                int dHeight = iSource.Height / 2;
                int dWidth = iSource.Width / 2;
                int sW = 0, sH = 0;
                //按比例缩放
                var tem_size = new System.Drawing.Size(iSource.Width, iSource.Height);
                if (tem_size.Width > dHeight || tem_size.Width > dWidth)
                {
                    if ((tem_size.Width * dHeight) > (tem_size.Width * dWidth))
                    {
                        sW = dWidth; sH = Convert.ToInt32((dWidth * tem_size.Height) / tem_size.Width);
                    }
                    else
                    {
                        sH = dHeight;
                        sW = Convert.ToInt32((tem_size.Width * dHeight) / tem_size.Height);
                    }
                }
                else
                {
                    sW = Convert.ToInt32(tem_size.Width);
                    sH = Convert.ToInt32(tem_size.Height);
                }
                ob = new Bitmap(dWidth, dHeight);
                var g = Graphics.FromImage(ob);
                g.Clear(System.Drawing.Color.WhiteSmoke);
                g.CompositingQuality = System.Drawing.Drawing2D.CompositingQuality.HighQuality;
                g.SmoothingMode = System.Drawing.Drawing2D.SmoothingMode.HighQuality;
                g.InterpolationMode = System.Drawing.Drawing2D.InterpolationMode.HighQualityBicubic;
                g.DrawImage(iSource, new Rectangle((dWidth - sW) / 2, (dHeight - sH) / 2, sW, sH), 0, 0, iSource.Width, iSource.Height, GraphicsUnit.Pixel);
                g.Dispose();
                //以下代码为保存图片时，设置压缩质量
                var ep = new EncoderParameters();
                var qy = new long[1];
                qy[0] = flag; //设置压缩的比例1-100
                var eParam = new EncoderParameter(System.Drawing.Imaging.Encoder.Quality, qy);
                ep.Param[0] = eParam;

                ImageCodecInfo[] arrayICI = ImageCodecInfo.GetImageEncoders();
                ImageCodecInfo jpegICIinfo = null;
                for (int x = 0; x < arrayICI.Length; x++)
                {
                    if (arrayICI[x].FormatDescription.Equals("JPEG"))
                    {
                        jpegICIinfo = arrayICI[x]; break;
                    }
                }
                result = new MemoryStream();
                if (jpegICIinfo != null)
                {
                    ob.Save(result, jpegICIinfo, ep);
                    if (result.Length > 1024 * size)
                    {
                        flag -= 10;
                        result = CompressImage(result, flag, size, false);
                    }
                }
                else
                {
                    ob.Save(result, tFormat);
                }
            }
            catch
            {
            }
            finally
            {
                iSource?.Dispose();
                ob.Dispose();
            }
            result?.Seek(0, SeekOrigin.Begin);
            return result;
        }

        /// <summary>
        /// 获取当前计算机MD5, 由CPUID,HardDiskSerialNumber 组成
        /// </summary>
        /// <returns></returns>
        public static string MachineMD5()
        {
            var objRegistryKey = Registry.LocalMachine.CreateSubKey(
    @"SOFTWARE\EntranceGuard");

            var code = objRegistryKey.GetValue("LicenseCode")?.ToString();

            if (string.IsNullOrEmpty(code))
            {
                code = $"{Guid.NewGuid().ToString("N")}{CPUID()}{HardDiskSerialNumber()}".MDString();
                objRegistryKey.SetValue("LicenseCode", code);
            }

            objRegistryKey.Close();

            return code;
        }

        public static string CPUID()
        {
            var result = string.Empty;
            try
            {
                using (var mc = new ManagementClass("Win32_Processor"))
                {
                    using (var collection = mc.GetInstances())
                    {
                        foreach (var item in collection)
                        {
                            result = item.Properties["ProcessorId"]?.Value?.ToString() ?? string.Empty;
                            if (!string.IsNullOrEmpty(result))
                            {
                                break;
                            }
                        }
                    }
                }

            }
            catch
            {

            }
            return result;
        }

        public static string HardDiskSerialNumber()
        {
            var result = string.Empty;
            try
            {
                using (var mc = new ManagementClass("Win32_DiskDrive"))
                {
                    using (var collection = mc.GetInstances())
                    {
                        foreach (var item in collection)
                        {
                            result = item.Properties["SerialNumber"]?.Value?.ToString() ?? string.Empty;
                            if (!string.IsNullOrEmpty(result))
                            {
                                break;
                            }
                        }
                    }
                }

            }
            catch
            {

            }
            return result;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="localFile"></param>
        /// <param name="needHeader"></param>
        /// <param name="compress"></param>
        /// <param name="compressTargetSize">压缩到指定文件大小, kb</param>
        /// <returns></returns>
        public static string GetBase64FromLocalFile(string localFile, bool needHeader = true,
            bool compress = true, int compressTargetSize = 200)
        {
            if (string.IsNullOrWhiteSpace(localFile)
                || !System.IO.File.Exists(localFile))
            {
                return string.Empty;
            }

            try
            {
                var ext = System.IO.Path.GetExtension(localFile).Replace(".", "");
                var header = needHeader ? $"data:image/{ext};base64," : "";

                if (compress)
                {
                    using var fs = new FileStream(localFile, FileMode.Open);
                    using var stream = CompressImage(fs, size: compressTargetSize);
                    var bytes = new byte[stream.Length];
                    stream.Read(bytes, 0, bytes.Length);
                    return $"{header}{Convert.ToBase64String(bytes)}";
                }

                return $"{header}{Convert.ToBase64String(System.IO.File.ReadAllBytes(localFile))}";
            }
            catch (Exception)
            {
                return string.Empty;
            }

        }

        public static string GetBase64FromLocalOrHttpFile(string localOrHttpFile, bool needHeader = true,
            bool compress = true, int compressTargetSize = 200)
        {
            if (string.IsNullOrWhiteSpace(localOrHttpFile))
            {
                Logger?.Info($"转换文件为Base64失败:参数为空");
                return string.Empty;
            }

            try
            {
                var stream = GetImageStreamFromLocalOrHttp(localOrHttpFile, out var err);
                if (stream == null)
                {
                    Logger?.Error($"转换文件 {localOrHttpFile} 为Base64失败:{err}");
                    return string.Empty;
                }

                return GetBase64FromStream(stream, Path.GetExtension(localOrHttpFile),
                    needHeader, compress, compressTargetSize);
            }
            catch (Exception e)
            {
                Logger?.Error($"转换文件 {localOrHttpFile} 为Base64失败:{e.Message}");
                return string.Empty;
            }

        }

        public static string GetBase64FromStream(Stream stream, string fileExt, bool needHeader = true,
            bool compress = true, int compressTargetSize = 200)
        {
            if (stream == null)
            {
                Logger?.Error($"转换流为Base64失败:参数为null");
                return string.Empty;
            }

            try
            {
                var header = needHeader ? $"data:image/{fileExt};base64," : "";
                if (compress)
                {
                    using var innerStreamstream = CompressImage(stream, size: compressTargetSize);
                    var bytes = new byte[innerStreamstream.Length];
                    innerStreamstream.Read(bytes, 0, bytes.Length);
                    return $"{header}{Convert.ToBase64String(bytes)}";
                }
                if (stream.CanSeek)
                {
                    stream.Seek(0, SeekOrigin.Begin);
                }
                using (stream)
                {
                    using var ms = new MemoryStream();
                    stream.CopyTo(ms);
                    return $"{header}{Convert.ToBase64String(ms.ToArray())}";
                }
            }
            catch (Exception e)
            {
                Logger?.Error($"转换流为Base64失败:{e.Message}");
                return string.Empty;
            }
        }

        public static void CreateShortcut(string exeName, string description, Assembly assembly = null)
        {
            var linkFile = Path.Combine(Environment.GetFolderPath(Environment.SpecialFolder.Desktop), $"{exeName}.lnk");
            if (System.IO.File.Exists(linkFile))
            {
                return;
            }
            try
            {
                if (assembly == null)
                {
                    assembly = Assembly.GetExecutingAssembly();
                }
                var location = assembly.Location.Replace(".dll", ".exe");
                var shell = new IWshRuntimeLibrary.WshShell();
                IWshRuntimeLibrary.IWshShortcut shortcut = (IWshRuntimeLibrary.IWshShortcut)shell.CreateShortcut(linkFile);
                shortcut.TargetPath = location;
                shortcut.WorkingDirectory = Path.GetDirectoryName(location);
                shortcut.Description = description;
                shortcut.IconLocation = $"{location},0";
                shortcut.Save();
            }
            catch
            {
            }
        }

        public static Process CreateCommand(string exeFile, string arguments)
        {
            var process = new Process();
            process.StartInfo.FileName = exeFile;
            process.StartInfo.UseShellExecute = false;    //是否使用操作系统shell启动
            process.StartInfo.RedirectStandardInput = true;//接受来自调用程序的输入信息
            process.StartInfo.RedirectStandardOutput = true;//由调用程序获取输出信息
            process.StartInfo.RedirectStandardError = true;//重定向标准错误输出
            process.StartInfo.CreateNoWindow = true;//不显示程序窗口
            process.StartInfo.Arguments = arguments;

            return process;
        }

        public static (string host, int port, string user, string database, string password) DecryptMySqlConnStr(string connStr)
        {
            var array = connStr.Split(';');

            var fields = new string[] { "server", "port", "user", "database", "password" };

            var dic = new Dictionary<string, string>();
            foreach (var item in array)
            {
                var parts = item.Split('=');
                var key = (parts.ElementAt(0) ?? string.Empty).ToLower();
                if (fields.Contains(key))
                {
                    dic.Add(key, parts.ElementAt(1));
                }
            }

            if (!dic.ContainsKey("port"))
            {
                dic.Add("port", "3306");
            }

            var port = dic[fields[1]].TryGetInt();

            return (dic[fields[0]], port, dic[fields[2]], dic[fields[3]], dic[fields[4]]);
        }

        public static string GetLocalIPV4()
        {
            var interfaces = NetworkInterface.GetAllNetworkInterfaces();
            foreach (NetworkInterface adapter in interfaces)
            {
                if (!string.IsNullOrEmpty(adapter.Description)
                    && adapter.Description.Contains("Hyper-V", StringComparison.OrdinalIgnoreCase))
                {
                    continue;
                }
                if (adapter.OperationalStatus != OperationalStatus.Up || adapter.NetworkInterfaceType == NetworkInterfaceType.Loopback)
                {
                    continue;
                }
                var properties = adapter.GetIPProperties();
                foreach (var uniAddress in properties.UnicastAddresses)
                {
                    if (uniAddress.Address.AddressFamily != System.Net.Sockets.AddressFamily.InterNetwork
                        || IPAddress.IsLoopback(uniAddress.Address))
                    {
                        continue;
                    }
                    return uniAddress.Address.ToString();
                }
            }
            return string.Empty;
        }

        /// <summary>
        /// 添加环境变量
        /// </summary>
        /// <param name="paths">路径列表</param>
        public static void AddEnvironmentPaths(IEnumerable<string> paths)
        {
            var path = new[] { Environment.GetEnvironmentVariable("PATH") ?? string.Empty };
            string newPath = string.Join(Path.PathSeparator.ToString(), path.Concat(paths));
            Environment.SetEnvironmentVariable("PATH", newPath);   // 这种方式只会修改当前进程的环境变量
        }

        private static readonly string[] _sizeUnits = new string[] { "B", "K", "M", "G", "TB" };

        public static string FormatFileSize(long size)
        {
            var index = 0;
            double sizeVal = size;
            if (size > 1024)
            {
                for (index = 0; (size / 1024L) > 0; index++, size /= 1024L)
                {
                    sizeVal = size / 1024.0;
                }
            }
            return string.Format("{0:0.##}{1}", sizeVal, _sizeUnits[index]);
        }

        public static void TryDeleteFiles(IEnumerable<string> files)
        {
            try
            {
                foreach (var file in files)
                {
                    if (File.Exists(file))
                    {
                        File.Delete(file);
                    }
                }
            }
            catch
            {
            }
        }

        public static bool TryCopyFile(string source, string target, out string errMsg)
        {
            try
            {
                if (!File.Exists(source))
                {
                    errMsg = "源文件不存在";
                    return false;
                }

                var dic = Path.GetDirectoryName(target);

                if (!Directory.Exists(dic))
                {
                    Directory.CreateDirectory(dic);
                }

                File.Copy(source, target, true);
                errMsg = string.Empty;
                return true;
            }
            catch (Exception e)
            {
                errMsg = e.Message;
                return false;
            }
        }
        public static bool TryCopyFileWithNoTry(string source, string target)
        {
            if (!File.Exists(source))
            {
                return false;
            }

            var dic = Path.GetDirectoryName(target);

            if (!Directory.Exists(dic))
            {
                Directory.CreateDirectory(dic);
            }

            File.Copy(source, target, true);
            return true;
        }


        /// <summary>
        /// 解压ZIP 
        /// </summary>
        /// <param name="zipFileName">zip文件 C:/data/a.zip</param>
        /// <param name="targetDirectory">解压到的目标路径 C:/data/temp</param>
        /// <returns></returns>
        public static bool ZIPUnpack(string zipFileName, string targetDirectory,
            Action<string, Exception> logHandler = null)
        {
            try
            {
                if (!Directory.Exists(targetDirectory))
                {
                    Directory.CreateDirectory(targetDirectory);
                }
                (new FastZip()).ExtractZip(zipFileName, targetDirectory, "");
                return true;
            }
            catch (Exception e)
            {
                logHandler?.Invoke(e.Message, e);
                return false;
            }

        }

        /// <summary>
        /// 压缩指定目录的所有文件,不包含嵌套的文件夹
        /// </summary>
        /// <param name="sourceDirectory">源文件目录, 如 C:/uplodas/images</param>
        /// <param name="zipFilePathName">zip文件路径 如 C:/uploads/files/pack.zip</param>
        /// <param name="level">压缩级别, 0 - 9, 越高压缩文件越小,但是速度越慢</param>
        /// <param name="fileNamePattern">要压缩的文件类型 如 *.jpg</param>
        /// <param name="deleteOriginalFile">压缩完毕是否删除源文件</param>
        public static bool ZIPPack(string sourceDirectory,
            string zipFilePathName,
            int level = 0,
            string fileNamePattern = "*.xlsx",
            bool deleteOriginalFile = true,
            Action<string, Exception> logHandler = null)
        {
            if (level < 0)
            {
                level = 0;
            }
            if (level > 9)
            {
                level = 9;
            }
            try
            {


                var files = Directory
                        .GetFiles(sourceDirectory, fileNamePattern)
                        .Select(p => new FileInfo(p)).ToList();

                if (files == null || files.Count == 0)
                {
                    return false;
                }

                using (var zipStream = new ZipOutputStream(File.Open(zipFilePathName, FileMode.OpenOrCreate)))
                {
                    zipStream.SetLevel(level);

                    foreach (var file in files)
                    {
                        using (var fs = File.OpenRead(file.FullName))
                        {
                            var buffer = new byte[fs.Length];
                            fs.Read(buffer, 0, buffer.Length);

                            zipStream.PutNextEntry(new ZipEntry(file.Name));
                            zipStream.Write(buffer, 0, buffer.Length);
                        }
                    }
                }

                if (deleteOriginalFile)
                {
                    foreach (var item in files)
                    {
                        item.Delete();
                    }
                }
            }
            catch (Exception e)
            {
                logHandler?.Invoke(e.Message, e);
                return false;
            }
            return true;
        }

        public static string AJSerializeObject<T>(T obj, JsonSerializerSettings settings = null)
        {
            settings ??= CAMELCASEJSONSERIALIZERSETTINGS;
            return JsonConvert.SerializeObject(obj, settings);
        }

        public static BitmapImage CreateBitmapImageFromStream(Stream stream)
        {
            if (stream == null)
            {
                return null;
            }
            var result = new BitmapImage();

            using var reader = new BinaryReader(stream);

            result.BeginInit();
            result.CacheOption = BitmapCacheOption.OnLoad;

            result.StreamSource = new MemoryStream(reader.ReadBytes(Convert.ToInt32(stream.Length)));
            result.EndInit();

            stream.Dispose();

            return result;
        }

        /// <summary>
        /// 获取本地或网络图片文件流,失败则返回null
        /// </summary>
        /// <param name="file"></param>
        /// <returns></returns>
        public static Stream GetImageStreamFromLocalOrHttp(string file, out string err)
        {
            Stream fs = null;

            if (string.IsNullOrWhiteSpace(file) || !CommonRegex.IMAGEREGEX.IsMatch(Path.GetExtension(file)))
            {
                err = "文件路径有误或者非图片格式";
                return fs;
            }
            try
            {
                if (CommonRegex.HTTPURLREGEX.IsMatch(file))
                {
                    try
                    {
                        var handler = new HttpClientHandler
                        {
                            AllowAutoRedirect = false,
                            ServerCertificateCustomValidationCallback
                            = (message, cert, chain, errors) => { return true; }
                        };
                        using var client = new HttpClient(handler, true);
                        client.DefaultRequestHeaders.TryAddWithoutValidation("User-Agent", "Mozilla/5.0 (Windows NT 10.0; Win64; x64) AppleWebKit/537.36 (KHTML, like Gecko) Chrome/125.0.0.0 Safari/537.36 Edg/125.0.0.0");
                        client.DefaultRequestHeaders.Add("Accept", "*/*");
                        client.Timeout = TimeSpan.FromSeconds(10);
                        var task = client.GetAsync(new Uri(WebUtility.HtmlDecode(file)));
                        task.Wait();
                        if (task.Result.StatusCode == HttpStatusCode.OK)
                        {
                            var resTask = task.Result.Content.ReadAsStreamAsync();
                            resTask.Wait();
                            fs = resTask.Result;
                        }
                        err = string.Empty;
                    }
                    catch (Exception e)
                    {
                        err = e.Message;
                    }
                }
                else
                {
                    if (File.Exists(file))
                    {
                        using var newfs = new FileStream(file, FileMode.Open, FileAccess.Read, FileShare.Read);
                        fs = new MemoryStream();
                        newfs.CopyTo(fs);
                        fs.Seek(0, SeekOrigin.Begin);
                        err = string.Empty;
                    }
                    else
                    {
                        err = $"文件:{file}不存在";
                    }
                }
            }
            catch (Exception e)
            {
                err = e.Message;
            }

            return fs;
        }

        public static bool CopyFile(string source, string target)
        {

            if (!File.Exists(source))
            {
                return false;
            }

            try
            {
                var dic = Path.GetDirectoryName(target);

                if (!Directory.Exists(dic))
                {
                    Directory.CreateDirectory(dic);
                }
                File.Copy(source, target, true);
                return true;
            }
            catch
            {
                return false;
            }
        }

        public static Dictionary<string, T> EnumToDictionary<T>(Func<T, string> keyFormatHandler) where T : Enum
        {
            var result = new Dictionary<string, T>();
            var array = Enum.GetValues(typeof(T));
            foreach (T item in array)
            {
                result.Add(keyFormatHandler?.Invoke(item) ?? item.ToString(), item);
            }
            return result;
        }

        /// <summary>
        /// 将 source 的属性值复制到 org 中
        /// </summary>
        /// <typeparam name="T"></typeparam>
        /// <param name="org"></param>
        /// <param name="source"></param>
        public static void CopyPropertyValues<T>(T org, T source)
        {
            var props = org.GetType().GetRuntimeProperties();
            var sourceProps = source.GetType().GetRuntimeProperties();

            foreach (var prop in props)
            {
                var attr = prop.GetCustomAttribute<AJNotCopyFieldAttribute>();
                if (attr != null)
                {
                    continue;
                }
                var sourceProp = sourceProps.FirstOrDefault(p => p.Name == prop.Name);

                prop.SetValue(org, sourceProp.GetValue(source));
            }
        }

        /// <summary>
        /// 尝试转换json字符串为 T,如果转换失败,则直接返回 默认 T --阿吉 2021年6月18日17点02分
        /// </summary>
        /// <param name="json"></param>
        /// <returns></returns>
        public static T TryGetJSONObject<T>(string json, JsonSerializerSettings settings = null)
        {
            try
            {
                settings ??= CAMELCASEJSONSERIALIZERSETTINGS;
                return JsonConvert.DeserializeObject<T>(json, settings);
            }
            catch
            {
                return default;
            }
        }

        /// <summary>
        /// 尝试转换json字符串为 T
        /// </summary>
        /// <param name="json"></param>
        /// <param name="obj"></param>
        /// <returns></returns>
        public static bool TryGetJSONObject<T>(string json, out T obj, JsonSerializerSettings settings = null)
        {
            var result = true;
            try
            {
                settings ??= CAMELCASEJSONSERIALIZERSETTINGS;
                obj = JsonConvert.DeserializeObject<T>(json, settings);
            }
            catch
            {
                obj = default;
                result = false;
            }
            return result;
        }

        /// <summary>
        /// 尝试转换json字符串为 object
        /// </summary>
        /// <param name="json"></param>
        /// <param name="type"></param>
        /// <param name="data"></param>
        /// <returns></returns>
        public static bool TryGetJSONObject(string json, Type type, out object data, JsonSerializerSettings settings = null)
        {
            var result = true;
            try
            {
                settings ??= CAMELCASEJSONSERIALIZERSETTINGS;
                data = JsonConvert.DeserializeObject(json, type, settings);
            }
            catch
            {
                data = null;
                result = false;
            }
            return result;
        }

        public static Task<bool> ShowConfirmDialogAsync(ConfirmationDialogArguments confirmDialogArguments,
            string dialogHostId = "root")
        {
            if (!DialogHost.IsDialogOpen(dialogHostId))
            {
                return ConfirmationDialog.ShowDialogAsync(dialogHostId, confirmDialogArguments);
            }

            return Task.FromResult(false);
        }
    }
}
